package com.ay.smartpark.sdk.common.utils;

import com.alibaba.excel.ExcelWriter;
import com.alibaba.excel.metadata.Font;
import com.alibaba.excel.metadata.Sheet;
import com.alibaba.excel.metadata.TableStyle;
import com.alibaba.excel.support.ExcelTypeEnum;

import com.ay.smartpark.sdk.common.base.EasyExcelParams;
import org.apache.poi.ss.usermodel.IndexedColors;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import javax.servlet.ServletOutputStream;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.io.UnsupportedEncodingException;
import java.net.URLEncoder;
import java.util.List;

/**
 * servlet工具类,用于excel导出:初始化请求头、响应头、获取输出流
 */

public class ExcelUtil {
    private static final Logger logger = LoggerFactory.getLogger(ExcelUtil.class);

    /**
     * 下载EXCEL文件2007版本
     *
     * @throws IOException IO异常
     */
    public static void exportExcel2007Format(EasyExcelParams excelParams) throws IOException {
        if (excelParams.getData() != null) {
            templateExportExcel(excelParams, ExcelTypeEnum.XLSX);
        } else if (excelParams.getDataList() != null) {
            simpleExportExcel(excelParams, ExcelTypeEnum.XLSX);
        }
    }

    /**
     * 下载EXCEL文件2003版本
     *
     * @throws IOException IO异常
     */
    public static void exportExcel2003Format(EasyExcelParams excelParams) throws IOException {
        if (excelParams.getData() != null) {
            templateExportExcel(excelParams, ExcelTypeEnum.XLS);
        } else if (excelParams.getDataList() != null) {
            simpleExportExcel(excelParams, ExcelTypeEnum.XLS);
        }
    }

    /**
     * 根据参数和版本枚举导出excel文件（模板）
     *
     * @param excelParams
     * @param typeEnum
     * @throws IOException
     */
    private static void templateExportExcel(EasyExcelParams excelParams, ExcelTypeEnum typeEnum) throws IOException {
        HttpServletResponse response = excelParams.getResponse();
        ServletOutputStream out = response.getOutputStream();

        // ExcelWriter提供了多种构造方式，可自行查看选择所需要的
        ExcelWriter writer = new ExcelWriter(null, out, typeEnum,
                true, excelParams.getWriteHandler());

        // 设置web下载等的信息
        prepareResponds(excelParams.getFileName(), response, typeEnum);
        // 创建一个sheet
        Sheet sheet = new Sheet(1, 0, excelParams.getDataModelClazz());
        sheet.setSheetName(excelParams.getSheetName());

        // 设置列宽 设置每列的宽度
        sheet.setAutoWidth(Boolean.TRUE);
        // 用于设置 表格样式
        sheet.setTableStyle(createTableStyle());
        // 写入Excel中，也提供了多个重载方法，根据需要选择
        writer.write(excelParams.getData(), sheet);

        // 根据数据展示需要，用于合并单元格
        List<int[]> mergeList = excelParams.getMergeList();
        if (mergeList != null && mergeList.size() > 0) {
            mergeList.forEach(arr -> writer.merge(arr[0], arr[1], arr[2], arr[3]));
        }
        writer.finish();
        out.flush();
    }

    /**
     * 根据参数和版本枚举导出excel文件（无模板）
     *
     * @param excelParams
     * @param typeEnum
     * @throws IOException
     */
    private static void simpleExportExcel(EasyExcelParams excelParams, ExcelTypeEnum typeEnum) throws IOException {
        HttpServletResponse response = excelParams.getResponse();
        ServletOutputStream out = response.getOutputStream();

        // ExcelWriter提供了多种构造方式，可自行查看选择所需要的
        ExcelWriter writer = new ExcelWriter(null, out, typeEnum,
                true, excelParams.getWriteHandler());

        // 设置web下载等的信息
        prepareResponds(excelParams.getFileName(), response, typeEnum);
        // 创建一个sheet
        Sheet sheet = new Sheet(1, 0);
        sheet.setSheetName(excelParams.getSheetName());

        // 设置列宽 设置每列的宽度
        sheet.setAutoWidth(Boolean.TRUE);
        // 用于设置 表格样式
        sheet.setTableStyle(createTableStyle());

        // 写入Excel中，也提供了多个重载方法，根据需要选择
        writer.write1(excelParams.getDataList(), sheet, excelParams.getTable());

        // 根据数据展示需要，用于合并单元格
        List<int[]> mergeList = excelParams.getMergeList();
        if (mergeList != null && mergeList.size() > 0) {
            mergeList.forEach(arr -> writer.merge(arr[0], arr[1], arr[2], arr[3]));
        }
        writer.finish();
        out.flush();
    }

    /**
     * 将文件输出到浏览器（导出文件）
     *
     * @param response 响应
     * @param typeEnum excel类型
     */
    private static void prepareResponds(String fileName, HttpServletResponse response, ExcelTypeEnum typeEnum) throws UnsupportedEncodingException {
        fileName = URLEncoder.encode(fileName, "UTF-8");
        response.setContentType("multipart/form-data");
        response.setCharacterEncoding("utf8");
        response.setHeader("Content-Disposition", "attachment;filename=" + fileName + typeEnum.getValue());
    }

    /**
     * 初始化表格样式
     *
     * @return
     */
    public static TableStyle createTableStyle() {
        TableStyle tableStyle = new TableStyle();
        // 设置表头样式
        Font headFont = new Font();
        // 字体是否加粗
        headFont.setBold(false);
        // 字体大小
        headFont.setFontHeightInPoints((short) 16);
        // 字体
        headFont.setFontName("宋体");
        tableStyle.setTableHeadFont(headFont);
        // 设置表格主体样式
        Font contentFont = new Font();
        contentFont.setFontHeightInPoints((short) 12);
        contentFont.setFontName("宋体");
        tableStyle.setTableContentFont(contentFont);
        tableStyle.setTableContentBackGroundColor(IndexedColors.WHITE);
        return tableStyle;
    }
}
